home *** CD-ROM | disk | FTP | other *** search
/ C/C++ Users Group Library 1996 July / C-C++ Users Group Library July 1996.iso / vol_100 / 198_02 / window.c < prev    next >
C/C++ Source or Header  |  1990-01-21  |  23KB  |  877 lines

  1. /*
  2.  * Window management. Some of the functions are internal, and some are
  3.  * attached to keys that the user actually types.
  4.  */
  5.  
  6. #include        <stdio.h>
  7. #include        "estruct.h"
  8. #include    "edef.h"
  9.  
  10. #if    ST520 & MEGAMAX
  11. overlay    "window"
  12. #endif
  13.  
  14. /*
  15.  * Reposition dot in the current window to line "n". If the argument is
  16.  * positive, it is that line. If it is negative it is that line from the
  17.  * bottom. If it is 0 the window is centered (this is what the standard
  18.  * redisplay code does). With no argument it defaults to 0. Bound to M-!.
  19.  */
  20. reposition(f, n)
  21.     {
  22.     if (f == FALSE)    /* default to 0 to center screen */
  23.     n = 0;
  24.     curwp->w_force = n;
  25.     curwp->w_flag |= WFFORCE;
  26.     return (TRUE);
  27.     }
  28.  
  29. /*
  30.  * Refresh the screen. With no argument, it just does the refresh. With an
  31.  * argument it recenters "." in the current window. Bound to "C-L".
  32.  */
  33. refresh(f, n)
  34.     {
  35.     if (f == FALSE)
  36.         sgarbf = TRUE;
  37.     else
  38.         {
  39.         curwp->w_force = 0;             /* Center dot. */
  40.         curwp->w_flag |= WFFORCE;
  41.         }
  42.  
  43.     return (TRUE);
  44.     }
  45.  
  46. /*
  47.  * The command make the next window (next => down the screen) the current
  48.  * window. There are no real errors, although the command does nothing if
  49.  * there is only 1 window on the screen. Bound to "C-X C-N".
  50.  *
  51.  * with an argument this command finds the <n>th window from the top
  52.  *
  53.  */
  54. nextwind(f, n)
  55.  
  56. int f, n;    /* default flag and numeric argument */
  57.  
  58. {
  59.     register WINDOW *wp;
  60.     register int nwindows;        /* total number of windows */
  61.  
  62.     if (f) {
  63.  
  64.         /* first count the # of windows */
  65.         wp = wheadp;
  66.         nwindows = 1;
  67.         while (wp->w_wndp != NULL) {
  68.             nwindows++;
  69.             wp = wp->w_wndp;
  70.         }
  71.  
  72.         /* if the argument is negative, it is the nth window
  73.            from the bottom of the screen            */
  74.         if (n < 0)
  75.             n = nwindows + n + 1;
  76.  
  77.         /* if an argument, give them that window from the top */
  78.         if (n > 0 && n <= nwindows) {
  79.             wp = wheadp;
  80.             while (--n)
  81.                 wp = wp->w_wndp;
  82.         } else {
  83.             mlwrite("Window number out of range");
  84.             return(FALSE);
  85.         }
  86.     } else
  87.         if ((wp = curwp->w_wndp) == NULL)
  88.             wp = wheadp;
  89.     curwp = wp;
  90.     curbp = wp->w_bufp;
  91.     upmode();
  92.     return (TRUE);
  93. }
  94.  
  95. /*
  96.  * This command makes the previous window (previous => up the screen) the
  97.  * current window. There arn't any errors, although the command does not do a
  98.  * lot if there is 1 window.
  99.  */
  100. prevwind(f, n)
  101. {
  102.     register WINDOW *wp1;
  103.     register WINDOW *wp2;
  104.  
  105.     /* if we have an argument, we mean the nth window from the bottom */
  106.     if (f)
  107.         return(nextwind(f, -n));
  108.  
  109.     wp1 = wheadp;
  110.     wp2 = curwp;
  111.  
  112.     if (wp1 == wp2)
  113.         wp2 = NULL;
  114.  
  115.     while (wp1->w_wndp != wp2)
  116.         wp1 = wp1->w_wndp;
  117.  
  118.     curwp = wp1;
  119.     curbp = wp1->w_bufp;
  120.     upmode();
  121.     return (TRUE);
  122. }
  123.  
  124. /*
  125.  * This command moves the current window down by "arg" lines. Recompute the
  126.  * top line in the window. The move up and move down code is almost completely
  127.  * the same; most of the work has to do with reframing the window, and picking
  128.  * a new dot. We share the code by having "move down" just be an interface to
  129.  * "move up". Magic. Bound to "C-X C-N".
  130.  */
  131. mvdnwind(f, n)
  132.  
  133. int n;
  134.  
  135. {
  136.     return (mvupwind(f, -n));
  137. }
  138.  
  139. /*
  140.  * Move the current window up by "arg" lines. Recompute the new top line of
  141.  * the window. Look to see if "." is still on the screen. If it is, you win.
  142.  * If it isn't, then move "." to center it in the new framing of the window
  143.  * (this command does not really move "."; it moves the frame). Bound to
  144.  * "C-X C-P".
  145.  */
  146. mvupwind(f, n)
  147.     int n;
  148.  
  149.     {
  150.     register LINE *lp;
  151.     register int i;
  152.  
  153.     lp = curwp->w_linep;
  154.  
  155.     if (n < 0)
  156.         {
  157.         while (n++ && lp!=curbp->b_linep)
  158.             lp = lforw(lp);
  159.         }
  160.     else
  161.         {
  162.         while (n-- && lback(lp)!=curbp->b_linep)
  163.             lp = lback(lp);
  164.         }
  165.  
  166.     curwp->w_linep = lp;
  167.     curwp->w_flag |= WFHARD;            /* Mode line is OK. */
  168.  
  169.     for (i = 0; i < curwp->w_ntrows; ++i)
  170.         {
  171.         if (lp == curwp->w_dotp)
  172.             return (TRUE);
  173.         if (lp == curbp->b_linep)
  174.             break;
  175.         lp = lforw(lp);
  176.         }
  177.  
  178.     lp = curwp->w_linep;
  179.     i  = curwp->w_ntrows/2;
  180.  
  181.     while (i-- && lp != curbp->b_linep)
  182.         lp = lforw(lp);
  183.  
  184.     curwp->w_dotp  = lp;
  185.     curwp->w_doto  = 0;
  186.     return (TRUE);
  187.     }
  188.  
  189. /*
  190.  * This command makes the current window the only window on the screen. Bound
  191.  * to "C-X 1". Try to set the framing so that "." does not have to move on the
  192.  * display. Some care has to be taken to keep the values of dot and mark in
  193.  * the buffer structures right if the distruction of a window makes a buffer
  194.  * become undisplayed.
  195.  */
  196. onlywind(f, n)
  197. {
  198.         register WINDOW *wp;
  199.         register LINE   *lp;
  200.         register int    i;
  201.  
  202.         while (wheadp != curwp) {
  203.                 wp = wheadp;
  204.                 wheadp = wp->w_wndp;
  205.                 if (--wp->w_bufp->b_nwnd == 0) {
  206.                         wp->w_bufp->b_dotp  = wp->w_dotp;
  207.                         wp->w_bufp->b_doto  = wp->w_doto;
  208.                         wp->w_bufp->b_markp = wp->w_markp;
  209.                         wp->w_bufp->b_marko = wp->w_marko;
  210.                         wp->w_bufp->b_fcol  = wp->w_fcol;
  211.                 }
  212.                 free((char *) wp);
  213.         }
  214.         while (curwp->w_wndp != NULL) {
  215.                 wp = curwp->w_wndp;
  216.                 curwp->w_wndp = wp->w_wndp;
  217.                 if (--wp->w_bufp->b_nwnd == 0) {
  218.                         wp->w_bufp->b_dotp  = wp->w_dotp;
  219.                         wp->w_bufp->b_doto  = wp->w_doto;
  220.                         wp->w_bufp->b_markp = wp->w_markp;
  221.                         wp->w_bufp->b_marko = wp->w_marko;
  222.                         wp->w_bufp->b_fcol  = wp->w_fcol;
  223.                 }
  224.                 free((char *) wp);
  225.         }
  226.         lp = curwp->w_linep;
  227.         i  = curwp->w_toprow;
  228.         while (i-- > 0 && lback(lp) != curbp->b_linep)
  229.                 lp = lback(lp);
  230.         curwp->w_toprow = 0;
  231.         curwp->w_ntrows = term.t_nrow - 1 - menuflag;
  232.         curwp->w_linep  = lp;
  233.         curwp->w_flag  |= WFMODE|WFHARD;
  234.         return (TRUE);
  235. }
  236.  
  237. /*
  238.  * Delete the current window, placing its space in the window above,
  239.  * or, if it is the top window, the window below. Bound to C-X 0.
  240.  */
  241.  
  242. delwind(f,n)
  243.  
  244. int f, n;    /* arguments are ignored for this command */
  245.  
  246. {
  247.     register WINDOW *wp;    /* window to recieve deleted space */
  248.     register WINDOW *lwp;    /* ptr window before curwp */
  249.     register int target;    /* target line to search for */
  250.         LINE   *lp;
  251.  
  252.     /* if there is only one window, don't delete it */
  253.     if (wheadp->w_wndp == NULL) {
  254.         mlwrite("Can not delete this window");
  255.         return(FALSE);
  256.     }
  257.  
  258.     /* find window before curwp in linked list */
  259.     wp = wheadp;
  260.     lwp = NULL;
  261.     while (wp != NULL) {
  262.         if (wp == curwp)
  263.             break;
  264.         lwp = wp;
  265.         wp = wp->w_wndp;
  266.     }
  267.  
  268.     /* find recieving window and give up our space */
  269.     wp = wheadp;
  270.     if (curwp->w_toprow == 0) {
  271.         /* find the next window down */
  272.         target = curwp->w_ntrows + 1;
  273.         while (wp != NULL) {
  274.             if (wp->w_toprow == target)
  275.                 break;
  276.             wp = wp->w_wndp;
  277.         }
  278.         if (wp == NULL)
  279.             return(FALSE);
  280.  
  281.         wp->w_toprow = 0;
  282.         wp->w_ntrows += target;
  283.  
  284.         /* change starting location to keep dot on same screen line */
  285.         lp = wp->w_linep;
  286.         while (target-- > 0 && lback(lp) != wp->w_bufp->b_linep)
  287.             lp = lback(lp);
  288.         wp->w_linep  = lp;
  289.     } else {
  290.         /* find the next window up */
  291.         target = curwp->w_toprow - 1;
  292.         while (wp != NULL) {
  293.             if ((wp->w_toprow + wp->w_ntrows) == target)
  294.                 break;
  295.             wp = wp->w_wndp;
  296.         }
  297.         if (wp == NULL)
  298.             return(FALSE);
  299.         wp->w_ntrows += 1 + curwp->w_ntrows;
  300.     }
  301.  
  302.     /* get rid of the current window */
  303.     if (--curwp->w_bufp->b_nwnd == 0) {
  304.         curwp->w_bufp->b_dotp = curwp->w_dotp;
  305.         curwp->w_bufp->b_doto = curwp->w_doto;
  306.         curwp->w_bufp->b_markp = curwp->w_markp;
  307.         curwp->w_bufp->b_marko = curwp->w_marko;
  308.                 curwp->w_bufp->b_fcol  = curwp->w_fcol;
  309.     }
  310.     if (lwp == NULL)
  311.         wheadp = curwp->w_wndp;
  312.     else
  313.         lwp->w_wndp = curwp->w_wndp;
  314.     free(